home *** CD-ROM | disk | FTP | other *** search
/ Developer CD Series 1997 February: Technology Seed / Mac Tech Seed Feb '97.toast / ODF Release 3 / ODFDev / Form / Sources / Dialog.cpp < prev    next >
Encoding:
Text File  |  1996-12-16  |  17.4 KB  |  532 lines  |  [TEXT/MPS ]

  1. //========================================================================================
  2. //
  3. //    File:                Dialog.cpp
  4. //    Release Version:    $ ODF 3 $
  5. //
  6. //    Copyright:            (c) 1993 - 1996 by Apple Computer, Inc., all rights reserved.
  7. //
  8. //========================================================================================
  9.  
  10. #include "Form.hpp"
  11.  
  12. #ifndef DIALOG_H
  13. #include "Dialog.h"
  14. #endif
  15.  
  16. #ifndef PART_H
  17. #include "Part.h"
  18. #endif
  19.  
  20. #ifndef FRAME_H
  21. #include "Frame.h"
  22. #endif
  23.  
  24. #ifndef VIEW_H
  25. #include "View.h"
  26. #endif
  27.  
  28. #ifndef DEFINES_K
  29. #include "Defines.k"
  30. #endif
  31.  
  32. // ----- Framework Layer -----
  33.  
  34. #ifndef FWEDVIEW_H
  35. #include "FWEdView.h"
  36. #endif
  37.  
  38. #ifndef FWSTATIC_H
  39. #include "FWStatic.h"
  40. #endif
  41.  
  42. #ifndef FWUTIL_H
  43. #include "FWUtil.h"
  44. #endif
  45.  
  46. #ifndef FWCONTXT_H
  47. #include "FWContxt.h"
  48. #endif
  49.  
  50. #ifndef FWBUTTON_H
  51. #include "FWButton.h"
  52. #endif
  53.  
  54. #ifndef FWKEYF_H
  55. #include "FWKeyF.h"
  56. #endif
  57.  
  58. #ifndef FWNOTDEF_H
  59. #include "FWNotDef.h"
  60. #endif
  61.  
  62. // ----- OS Layer -----
  63.  
  64. #ifndef FWMENU_H
  65. #include "FWMenu.h"
  66. #endif
  67.  
  68. #ifndef FWEVENT_H
  69. #include "FWEvent.h"
  70. #endif
  71.  
  72. #ifndef FWALERT_H
  73. #include "FWAlert.h"
  74. #endif
  75.  
  76. #ifndef SLMixOS_H
  77. #include "SLMixOS.h"
  78. #endif
  79.  
  80. #ifndef FWCFMRES_H
  81. #include "FWCFMRes.h"
  82. #endif
  83.  
  84. // ----- Graphic Includes -----
  85.  
  86. #ifndef FWRECT_H
  87. #include "FWRect.h"
  88. #endif
  89.  
  90. #ifndef FWTXTBOX_H
  91. #include "FWTxtBox.h"
  92. #endif
  93.  
  94. #ifndef FWRECSHP_H
  95. #include "FWRecShp.h"
  96. #endif
  97.  
  98. // ----- Foundation Layer -----
  99.  
  100. #ifndef FWEXCDEF_H
  101. #include "FWExcDef.h"
  102. #endif
  103.  
  104. #ifndef FWNOTIFN_H
  105. #include "FWNotifn.h"
  106. #endif
  107.  
  108. #ifndef FWMEMMGR_H
  109. #include "FWMemMgr.h"
  110. #endif
  111.  
  112. // ----- PPob View Support -----
  113.  
  114. #if FW_PPOB_VIEWS
  115. #include "FWPPobRd.h"
  116. #endif
  117.  
  118. // Check that Form is using only 1 view system!
  119. #if (FW_ODFRC_VIEWS && FW_PPOB_VIEWS)
  120. #include "Error in Defines.k: define only 1 flag FW_XXXX_VIEWS at a time!"
  121. #endif
  122.  
  123. //========================================================================================
  124. // Runtime Informations
  125. //========================================================================================
  126.  
  127. #ifdef FW_BUILD_MAC
  128. #pragma segment odfform
  129. #endif
  130.  
  131. FW_DEFINE_AUTO(CPwdDialogFrame)
  132. FW_DEFINE_AUTO(CPwdEditView)
  133.  
  134. //========================================================================================
  135. // class CPwdDialogFrame 
  136. //========================================================================================
  137.  
  138. //----------------------------------------------------------------------------------------
  139. // CPwdDialogFrame::CPwdDialogFrame
  140. //----------------------------------------------------------------------------------------
  141. CPwdDialogFrame::CPwdDialogFrame(Environment* ev, ODFrame* odFrame, 
  142.                         FW_CPresentation* presentation,    CFormPart* part)
  143.     : FW_CDialogFrame(ev, odFrame, presentation, part) 
  144. {
  145.  
  146.     // If your modal dialog contains edit views which support Undo/Redo like CScrollEditView
  147.     // you should uncomment the following line to mark the Undo & Redo stacks
  148.     // This way you can clear the action history when the dialog is deleted (see below).    
  149. //    part->GetSession(ev)->GetUndo(ev)->MarkActionHistory(ev);
  150. }
  151.  
  152. //----------------------------------------------------------------------------------------
  153. // CPwdDialogFrame::~CPwdDialogFrame
  154. //----------------------------------------------------------------------------------------
  155.  
  156. CPwdDialogFrame::~CPwdDialogFrame()
  157. {
  158.     // If your modal dialog contains edit views which support Undo/Redo like CScrollEditView
  159.     // you should uncomment the following line to clear the Undo & Redo stacks
  160. //    GetPart(ev)->GetSession(ev)->GetUndo(ev)->ClearActionHistory(ev, kODRespectMarks);
  161. }
  162.  
  163. //----------------------------------------------------------------------------------------
  164. // CPwdDialogFrame::FacetAdded
  165. //----------------------------------------------------------------------------------------
  166. // On the Mac we need to add a color table to the dialog window in order to draw
  167. // a uniform gray background (otherwise the dialog frame keeps a white border)
  168.  
  169. #ifdef FW_BUILD_MAC
  170.  
  171. void CPwdDialogFrame::FacetAdded(Environment* ev, ODFacet* facet, unsigned short facetCount)
  172. {
  173.     FW_CDialogFrame::FacetAdded(ev, facet, facetCount);
  174.     
  175.     if (facetCount == 1)
  176.     {
  177.         ODPlatformWindow platformWindow = facet->GetWindow(ev)->GetPlatformWindow(ev);
  178.         
  179.         WCTabHandle newColorTable = (WCTabHandle)FW_CMemoryManager::AllocateSystemHandle
  180.                                                                     (8+sizeof(ColorSpec));
  181.         (*newColorTable)->ctSize = 0;
  182.         (*newColorTable)->ctTable[0].value = wContentColor;
  183.         (*newColorTable)->ctTable[0].rgb = FW_CColor(FW_kRGBLightGray);
  184.         ::SetWinColor(platformWindow, newColorTable);
  185.     }
  186. }
  187. #else
  188. //----------------------------------------------------------------------------------------
  189. // CPwdDialogFrame::Draw
  190. //----------------------------------------------------------------------------------------
  191.  
  192. void CPwdDialogFrame::Draw(Environment *ev, ODFacet* odFacet, ODShape* invalidShape)
  193. {
  194.     // Set drawing contect for the CFrame
  195.     FW_CViewContext vc(ev, this, odFacet, invalidShape);
  196.  
  197.     // Draw gray background
  198.     FW_CRectShape::RenderRect(vc, GetBounds(ev), FW_kFill, FW_kRGBLightGray);
  199.  
  200. }
  201. #endif // FW_BUILD_MAC
  202.  
  203. //----------------------------------------------------------------------------------------
  204. //    CPwdDialogFrame::PostCreateViewFromStream
  205. //----------------------------------------------------------------------------------------
  206. // PostCreateViewFromStream is called after subviews are created from resources.  
  207. // Implement initializations for this view that can't be done from a stream.
  208.  
  209. void CPwdDialogFrame::PostCreateViewFromStream(Environment* ev)
  210. {
  211.     // ----- Call inherited to propagate to all subviews if necessary
  212.     FW_CSuperView::PostCreateViewFromStream(ev);
  213.  
  214.     // ----- Add alpha-numeric keyfilters to edit views 
  215.     //        (will be deleted along with the edit views, they are adopted event handlers)
  216.     FW_CView* editView1 = FindViewByID(ev, kPasswordEditID);    
  217.     FW_CView* editView2 = FindViewByID(ev, kConfirmEditID);    
  218.     FW_ASSERT(editView1 && editView2);
  219.     
  220.     FW_CAlphaNumFilter* keyF1 = new FW_CAlphaNumFilter(ev, (FW_MEventHandler*)editView1);
  221.     FW_CAlphaNumFilter* keyF2 = new FW_CAlphaNumFilter(ev, (FW_MEventHandler*)editView2);
  222.     
  223.     // Note: OK and Cancel buttons are linked automatically to the dialogFrame by
  224.     //         defining FW_kDefaultButtonMsg and FW_kCancelButtonMsg in "Views.fr"
  225.  
  226.     // WARNING: Make sure that classes created from resources won't be dead-stripped
  227.     //            (here we don't need to worry about our custom class CPwdEditView
  228.     //            because all its implementation is compiled in this file)
  229.     FW_DO_NOT_DEAD_STRIP(FW_CButton);
  230.     FW_DO_NOT_DEAD_STRIP(FW_CStaticText);
  231. }
  232.  
  233. //----------------------------------------------------------------------------------------
  234. // CPwdDialogFrame::CreateSubViews
  235. //----------------------------------------------------------------------------------------
  236.  
  237. #if !FW_ODFRC_VIEWS
  238. void CPwdDialogFrame::CreateSubViews(Environment* ev)
  239. {        
  240. #if FW_PPOB_VIEWS
  241.     // Load views from PPob resources.
  242.     FW_CPPobReader::CreateViews (ev, kPasswordDialog, this, this);
  243. #endif
  244.  
  245. #if 0
  246.     // NOTE: CreateSubViews is not needed when the frame's ctor is passed a resource id.
  247.     //          This code was left here to show how to create views by program
  248.     FW_CRect viewRect;        // working rectangle for creating the views
  249.     
  250.     // ---- Create the static texts
  251.     viewRect.Set(FW_IntToFixed(20), FW_IntToFixed(40), FW_IntToFixed(140), FW_IntToFixed(70));
  252.     FW_CStaticText* staticText1 = FW_NEW(FW_CStaticText, (ev, this, viewRect, FW_CString("Pick a \rpassword:")));
  253.  
  254.     viewRect.Set(FW_IntToFixed(20), FW_IntToFixed(70), FW_IntToFixed(140), FW_IntToFixed(100));
  255.     FW_CStaticText* staticText2 = FW_NEW(FW_CStaticText, (ev, this, viewRect, FW_CString("Retype to \nverify:")));
  256.     
  257.     // ---- Create the text edit controls using our custom Edit Views
  258.     viewRect.Set(FW_IntToFixed(150), FW_IntToFixed(40), FW_IntToFixed(280), FW_IntToFixed(60));
  259.     CPwdEditView* editView1 = FW_NEW(CPwdEditView, (ev, this, kPasswordEditID, viewRect));
  260.  
  261.     viewRect.Set(FW_IntToFixed(150), FW_IntToFixed(70), FW_IntToFixed(280), FW_IntToFixed(90));
  262.     CPwdEditView* editView2 = FW_NEW(CPwdEditView, (ev, this, kConfirmEditID, viewRect));
  263.     
  264.     // ----- Add alpha-numeric keyfilters to edit views
  265.     FW_CAlphaNumFilter* keyF1 = new FW_CAlphaNumFilter(ev, (FW_MEventHandler*)editView1);
  266.     FW_CAlphaNumFilter* keyF2 = new FW_CAlphaNumFilter(ev, (FW_MEventHandler*)editView2);
  267.     
  268.     // ----- Create the OK/Cancel buttons: 
  269.     //        - Use normal font instead of default system font
  270.     //        - Set the control message so that they are initialized as "default" and "cancel" 
  271.     //          dialog buttons  (no need to call SetDefaultButton() and SetCancelButton() later)
  272.     viewRect.Set(FW_IntToFixed(180), FW_IntToFixed(117), FW_IntToFixed(260), FW_IntToFixed(148));
  273.     FW_CButton* okButton = FW_NEW(FW_CButton, (ev, this, kOKButtonID, viewRect, FW_kPushButton, 
  274.                                         FW_CString("OK"), FW_kNormalFont, FW_kDefaultButtonMsg));
  275.  
  276.     viewRect.Set(FW_IntToFixed(60), FW_IntToFixed(123), FW_IntToFixed(140), FW_IntToFixed(145));
  277.     FW_CButton* cancelButton = FW_NEW(FW_CButton, (ev, this, kCancelButtonID, viewRect, FW_kPushButton, 
  278.                                         FW_CString("Cancel"), FW_kNormalFont, FW_kCancelButtonMsg));
  279. #endif
  280. }
  281. #endif
  282.  
  283. //----------------------------------------------------------------------------------------
  284. // CPwdDialogFrame::Initialize
  285. //----------------------------------------------------------------------------------------
  286. // You can group all additional dialog initialization in a local method like this one
  287. // or simply put the code after your call to FW_CDialogFrame::NewModalDialog 
  288.  
  289. void CPwdDialogFrame::Initialize(Environment* ev, CFormFrame* frame)
  290. {
  291. FW_UNUSED(ev);
  292.     fFormFrame = frame;
  293. }
  294.  
  295. //----------------------------------------------------------------------------------------
  296. //    CPwdDialogFrame::HandleNotification
  297. //----------------------------------------------------------------------------------------
  298.  
  299. void CPwdDialogFrame::HandleNotification(Environment* ev, const FW_CNotification& notification)
  300. {
  301.     // ---- Verify edit fields when clicking on OK button ----
  302.     if (notification.GetMessage() ==  FW_kDefaultButtonMsg) 
  303.     {
  304.         // Get the 2 edit views
  305.         FW_CView* view =  FindViewByID(ev, kPasswordEditID);
  306.         CPwdEditView* pwdTEd = FW_DYNAMIC_CAST(CPwdEditView, view);
  307.         FW_ASSERT(pwdTEd);
  308.         view =  FindViewByID(ev, kConfirmEditID);
  309.         CPwdEditView* confirmTEd = FW_DYNAMIC_CAST(CPwdEditView, view);
  310.         FW_ASSERT(confirmTEd);
  311.  
  312.         // Check that the password has at least 3 characters
  313.         FW_CString text = pwdTEd->GetText(ev);
  314.         
  315.         if (text.GetCharacterLength() < 3) {
  316.             // Open Alert and return to avoid closing the dialog
  317.             FW_ErrorAlert(FW_CString(), FW_CString("Password must contain at least 3 characters"));
  318.             return;
  319.         }
  320.         
  321.         // Check that both strings are equal
  322.         FW_CString text2 = confirmTEd->GetText(ev);
  323.         
  324.         if (text != text2) {
  325.             // Open Alert and return to avoid closing the dialog
  326.             FW_ErrorAlert(FW_CString(), FW_CString("Please re-type, strings don't match"));
  327.             return;
  328.         }
  329.         
  330.         // Password is OK, we can switch the form. 
  331.         CFormView* formView = (CFormView*) fFormFrame->GetContentView(ev);
  332.         formView->SwitchForm(ev);
  333.     } 
  334.     
  335.     // Must call inherited to close the dialog on OK & Cancel
  336.     // WARNING: do not do anything else after this call... the dialog is gone!
  337.     FW_CDialogFrame::HandleNotification(ev, notification);
  338. }
  339.  
  340. //========================================================================================
  341. // class CPwdEditView 
  342. //========================================================================================
  343.  
  344. FW_DEFINE_CLASS_M1(CPwdEditView, FW_CEditView);
  345.  
  346. const FW_ClassTypeConstant LPwdEditView = FW_TYPE_CONSTANT('P','w','d','v');
  347. FW_REGISTER_ARCHIVABLE_CLASS(LPwdEditView, CPwdEditView, CPwdEditView::Create, FW_CView::Read, CPwdEditView::Destroy, FW_CView::Write)
  348.  
  349. //----------------------------------------------------------------------------------------
  350. // CPwdEditView::CPwdEditView
  351. //----------------------------------------------------------------------------------------
  352. CPwdEditView::CPwdEditView(Environment* ev, 
  353.                         FW_CSuperView* container, 
  354.                         const FW_CRect& bounds,
  355.                         ODID viewID)
  356.     : FW_CEditView(ev, container, bounds, viewID) 
  357. {
  358.     Initialize(ev, container, bounds);
  359. }
  360.  
  361. //----------------------------------------------------------------------------------------
  362. // CPwdEditView::CPwdEditView
  363. //----------------------------------------------------------------------------------------
  364. CPwdEditView::CPwdEditView(Environment* ev)
  365.     : FW_CEditView(ev) 
  366. {
  367. }
  368.  
  369. //----------------------------------------------------------------------------------------
  370. // CPwdEditView::~CPwdEditView
  371. //----------------------------------------------------------------------------------------
  372.  
  373. CPwdEditView::~CPwdEditView()
  374. {
  375. }
  376.  
  377. //----------------------------------------------------------------------------------------
  378. // CPwdEditView::Initialize
  379. //----------------------------------------------------------------------------------------
  380.  
  381. void CPwdEditView::Initialize(Environment* ev, FW_CSuperView* container, const FW_CRect& bounds)
  382. {
  383.     FW_CRect farBounds(bounds);
  384.     farBounds.Place(FW_IntToFixed(30000), FW_IntToFixed(30000));
  385.  
  386.     // Create a shadow edit view to hold the real text
  387.     // (Note: Making the view invisible is not enough to hide it because the Mac toolbox
  388.     //  will still draw the text being inserted with TEKey) 
  389.     fShadowTEd = FW_NEW(FW_CEditView, (ev, container, farBounds, FW_kNoViewID));
  390.     fShadowTEd->Disable(ev);
  391. }
  392.  
  393. //----------------------------------------------------------------------------------------
  394. // CPwdEditView::ActivateTarget
  395. //----------------------------------------------------------------------------------------
  396.  
  397. void CPwdEditView::ActivateTarget (Environment * ev, FW_Boolean tabSelection)
  398. {
  399.     // must select also the shadow TEd after a Tab
  400.     if (tabSelection)
  401.         fShadowTEd->SelectAll(ev);
  402.     
  403.     FW_CEditView::ActivateTarget(ev, tabSelection);
  404. }    
  405.  
  406. //----------------------------------------------------------------------------------------
  407. // CPwdEditView::DoMenu
  408. //----------------------------------------------------------------------------------------
  409.  
  410. FW_Handled CPwdEditView::DoMenu (Environment* ev, const FW_CMenuEvent& event)
  411. {
  412.     switch (event.GetCommandID(ev)) {
  413.         case kODCommandCut: 
  414.         case kODCommandCopy: 
  415.         case kODCommandPaste: 
  416.         case kODCommandClear: 
  417.             return FW_kHandled;
  418.         case kODCommandSelectAll: 
  419.             SelectAll(ev);
  420.             break;
  421.         default:
  422.             return FW_CView::DoMenu (ev, event);
  423.     }
  424.     return FW_kHandled;
  425. }
  426.  
  427. //----------------------------------------------------------------------------------------
  428. // CPwdEditView::DoCharKeyDown
  429. //----------------------------------------------------------------------------------------
  430.  
  431. FW_Handled CPwdEditView::DoCharKeyDown (Environment* ev, const FW_CCharKeyEvent & event)
  432. {
  433. #ifdef FW_BUILD_MAC
  434.     char bullet = 0xA5;
  435.  
  436.     if (event.IsItemModifier(ev))
  437.         return FW_kNotHandled;
  438. #endif
  439. #ifdef FW_BUILD_WIN
  440.     char bullet = '*';
  441. #endif
  442.  
  443.     // For printable chars use bullet in visible TEd instead of real char
  444.     char realChar = event.GetChar(ev);
  445.     char pwdChar = (realChar >= 0x20) ? bullet : realChar;
  446.     
  447.     // Make Backspace erase the whole text
  448.     if (realChar == 0x08) {
  449.         SelectAll(ev);
  450.         fShadowTEd->SelectAll(ev);
  451.     }
  452.     
  453.     InputCharKey(ev, pwdChar); 
  454.     return fShadowTEd->InputCharKey(ev, realChar);
  455. }
  456.  
  457. //----------------------------------------------------------------------------------------
  458. // CPwdEditView::GetText
  459. //----------------------------------------------------------------------------------------
  460.  
  461. FW_CString CPwdEditView::GetText (Environment * ev)
  462. {
  463.     return fShadowTEd->GetText(ev);
  464. }
  465.  
  466.  
  467. //========================================================================================
  468. //    Archiving API with ODFRC resources
  469. //========================================================================================
  470. #if FW_ODFRC_VIEWS
  471.  
  472. //----------------------------------------------------------------------------------------
  473. //    CPwdEditView::Create
  474. //----------------------------------------------------------------------------------------
  475.  
  476. void* CPwdEditView::Create(FW_CReadableStream& stream, FW_ClassTypeConstant type)
  477. {
  478. FW_UNUSED(stream);
  479. FW_UNUSED(type);
  480.     FW_SOMEnvironment ev;
  481.     return FW_NEW(CPwdEditView, (ev));
  482. }
  483.  
  484. //----------------------------------------------------------------------------------------
  485. //    CPwdEditView::Destroy
  486. //----------------------------------------------------------------------------------------
  487.  
  488. void CPwdEditView::Destroy(void* object, FW_ClassTypeConstant type)
  489. {
  490. FW_UNUSED(type);
  491.     CPwdEditView* self = (CPwdEditView*) object;
  492.     delete self;
  493. }
  494.  
  495. //----------------------------------------------------------------------------------------
  496. //    CPwdEditView::Flatten
  497. //----------------------------------------------------------------------------------------
  498.  
  499. void CPwdEditView::Flatten(Environment* ev, FW_CWritableStream& archive) const
  500. {
  501.     FW_CEditView::Flatten(ev, archive);
  502. }
  503.  
  504. //----------------------------------------------------------------------------------------
  505. //    CPwdEditView::InitializeFromStream
  506. //----------------------------------------------------------------------------------------
  507.  
  508. void CPwdEditView::InitializeFromStream(Environment* ev, FW_CReadableStream& stream)
  509. {
  510.     FW_CEditView::InitializeFromStream(ev, stream);
  511.     
  512.     Initialize(ev, GetSuperView(ev), GetBounds(ev));
  513. }
  514.  
  515. #endif // FW_ODFRC_VIEWS
  516.  
  517. //========================================================================================
  518. // MetroWerks Constructor View Resource Reader
  519. //========================================================================================
  520. #if FW_PPOB_VIEWS
  521.  
  522. void ReadPasswordEditView (Environment* ev, FW_CPPobReader* context, FW_CReadableStream& stream)
  523. {
  524.     FW_SPPobEditInfo info (stream);
  525.     
  526.     CPwdEditView* view = FW_NEW (CPwdEditView, (ev, context->GetSuperView(), info.fBounds, info.fViewID));
  527.     view->SetBindings (ev, info.fBindings);
  528. }
  529.  
  530. #endif // FW_PPOB_VIEWS
  531.  
  532.